<style lang="scss" scoped>
    .echart-cont {
        position: relative;
        width: 100%;
        height: 100%;
    }

    .full {
        position: absolute;
        width: 100%;
        height: 100%;
    }
</style>
<template>
    <div class="echart-cont">
        <!--此容器作用在于,防止chart在初始化时撑开弹性容器-->
        <div ref="echart" class="full" :style="{width:width, height:height}"></div>
    </div>
</template>
<script>
    import ResizeObserver from 'resize-observer-polyfill'

    let resizeObserver

    export default {
        name: 'ui-echarts',
        props: {
            // echarts的配置项
            option: { type: Object },
            width: { type: String },
            height: { type: String },
            merge: { type: Boolean },
            dark: { type: Boolean },
            plugin: { type: Array },
            callback: { type: Function }
        },
        data() {
            return {
                chart: null, //chart实例
                resizeTimer: null, //resize触发间隔
                init: false
            }
        },
        created() {

        },
        watch: {
            option: {
                handler(v) {
                    if (this.chart && v) {
                        if (!this.init) {
                            this.initChart()
                        }
                        // 更新echart
                        this.chart.setOption(v, {
                            notMerge: this.merge, //可选，是否不跟之前设置的option进行合并，默认为false，即合并。
                            lazyUpdate: false, //可选，在设置完option后是否不立即更新图表，默认为false，即立即更新。
                            silent: false //可选，阻止调用 setOption 时抛出事件，默认为false，即抛出事件。
                        })
                    }
                },
                deep: true
            }
        },
        methods: {
            initChart() {
                if (!window.echarts)  return

                // 初始化实例
                this.chart = window.echarts.init(this.$refs['echart'], this.dark ? 'dark' : 'light')
                // 如果有配置项,初始就渲染
                this.option && this.chart.setOption(this.option)
                // 点击事件
                this.chart.on('click', (params) => {
                    this.$emit('node-click', params)
                })
                this.init = true;
            },
            resize() {
                clearTimeout(this.resizeTimer)
                this.resizeTimer = setTimeout(() => {
                    // console.log(this.chart)
                    this.chart.resize()
                    this.resizeTimer = null
                }, 300)
            },
            InsChart() {
                return new Promise((resolve) => {
                        const url = (process.env.NODE_ENV === 'production') ? BASE_URL + 'bui/static/libs/echarts/echarts.min.js' : BASE_URL + 'bui/static/libs/echarts/echarts.min.js'
                        this.$bui.jsLoader(url, window.echarts).then(() => {
                        if (window.echarts.version && window.echarts.version[0] < 4) {
                            console.warn('echarts版本过低,请更新代码后运行\n npm update echarts')
                        }

                          let path = (process.env.NODE_ENV === 'production') ? BASE_URL + 'bui/static/libs/echarts/dark.js' : BASE_URL + 'static/libs/echarts/dark.js'
                        // 载入插件
                        if (this.plugin) {
                            path = [path, ...this.plugin]
                        }
                        // 如果存在深色主题
                        if (this.dark) {
                            this.$bui.jsLoader(path, window.echarts.hasRegisterTheme).then(() => {
                                // 像全局提交一个echats已经载入的信号
                                // console.log('echarts init over')
                                this.initChart()
                                if (this.plugin) {
                                    this.$emit('global:ECHARTS_LOADED_ALL')
                                }else{
                                    this.$emit('global:ECHARTS_LOADED')
                                }
                                // 执行callback
                                this.callback && this.callback(this.chart)
                                resolve(this.chart)
                            })
                        }else{
                            this.initChart()
                            // 像全局提交一个echats已经载入的信号
                            this.$emit('global:ECHARTS_LOADED')
                            // 执行callback
                            this.callback && this.callback(this.chart)
                            resolve(this.chart)
                        }

                    })
                });
            }
        },
        mounted() {
            this.InsChart()

            // 绑定window resize
            // window.addEventListener('resize', this.resize)

            // 外部告诉echart需要重绘
            this.$eventHub.$on('echartResize', this.resize)

            // 当监听到父级容器尺寸变后执行一次虚拟数据重载
            let vm = this
            this.$nextTick(() => {
                if (!window.resizeObserver) {
                    resizeObserver = new ResizeObserver(() => {
                        if (vm.chart && vm.resize) {
                            vm.resize()
                        }
                    })
                    resizeObserver.observe(vm.$el)
                }
            })

        },
        beforeDestroy() {
            // 解绑window resize
            // window.removeEventListener('resize', this.resize)
            this.resize = null
            this.$eventHub.$off('echartResize', this.resize)

            // 销毁窗口监听
            resizeObserver.unobserve(this.$el)

        },
        destroyed() {
            // 销毁chart实例
            setTimeout(() => {
                this.chart.dispose()
            }, 300)

        }
    }
</script>
